#region Using Statements
using System;
using System.Collections.Generic;
using Microsoft.Xna.Framework;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework.Input;
using Microsoft.Xna.Framework.Graphics;
using Swarm_Defense;
using Camera_2DComponent;
#endregion

namespace MouseComponent
{
    /// <summary>
    /// This is a game component that implements IUpdateable.
    /// </summary>
    public class MouseClass : Microsoft.Xna.Framework.DrawableGameComponent
    {
        MouseState _mouse;
        Texture2D _mouseImage;
        SpriteBatch _spriteBatch;
        Game1 _game;
        SpriteFont ArialFont;

        bool _leftPress = false;
        bool _leftClick = false;

        List<Object_2D> lstPointer;

        private int _cyclesSinceLastHoverCheck = 0;


        public MouseClass(Game game)
            : base(game)
        {
            _game = (Game1) game;
            // TODO: Construct any child components here
        }


        /// <summary>
        /// Allows the game component to perform any initialization it needs to before starting
        /// to run.  This is where it can query for any required services and load content.
        /// </summary>
        public override void Initialize()
        {
            // TODO: Add your initialization code here

            base.Initialize();
        }

        protected override void LoadGraphicsContent(bool loadAllContent)
        {
            if (loadAllContent)
            {
                _spriteBatch = new SpriteBatch(GraphicsDevice);
                _mouseImage = Texture2D.FromFile(GraphicsDevice, @"Content\\RedMouse.png");
                // Set this to some incredibly high number so we are always on top.
                this.DrawOrder = 10000;
                ArialFont = _game.content.Load<SpriteFont>(@"Content\Fonts\Arial48");

            }
            base.LoadGraphicsContent(loadAllContent);
        }
        /// <summary>
        /// Allows the game component to update itself.
        /// </summary>
        /// <param name="gameTime">Provides a snapshot of timing values.</param>
        public override void Update(GameTime gameTime)
        {
            // TODO: Add your update code here
            _mouse = Mouse.GetState();
            ProcessState();

            if (_leftClick)
            {
                if (_game.MainMenu.Visible)
                {
                    lstPointer = _game.MainMenu.MenuItemList;
                }
                else
                {
                    lstPointer = _game.camera.ActiveObjects;
                }
                ClickCheck(lstPointer);
                ClearState();
            }
            else
            {
                _cyclesSinceLastHoverCheck += 1;
                if (_cyclesSinceLastHoverCheck > 10)
                {
                    if (_game.MainMenu.Visible)
                    {
                        lstPointer = _game.MainMenu.MenuItemList;
                    }
                    else
                    {
                        lstPointer = _game.camera.ActiveObjects;
                    }
                    HoverCheck(lstPointer);
                    _cyclesSinceLastHoverCheck = 0;
                }
            }
            base.Update(gameTime);
        }

        private void ProcessState()
        {
            if (_leftPress && (_mouse.LeftButton == ButtonState.Released))
            {
                _leftClick = true;
            }
            if (_mouse.LeftButton == ButtonState.Pressed)
            {
                _leftPress = true;
            }
        }

        private void ClearState()
        {
            _leftClick = false;
            _leftPress = false;
        }

        private void HoverCheck(List<Object_2D> ListIn)
        {
            for (int i = 0; i< ListIn.Count; i++)
            {
                /* Is the mouse inside our object's rectangle? */
                if (
                    ((_mouse.X > ListIn[i].Loc.X) && (_mouse.X < (ListIn[i].Loc.X + ListIn[i].Xsize))) &&
                    ((_mouse.Y > ListIn[i].Loc.Y) && (_mouse.Y < (ListIn[i].Loc.Y + ListIn[i].Ysize))) 
                    )
                {
                    ListIn[i].Hovered = true;
                }
                else
                {
                    ListIn[i].Hovered = false;
                }
            }
        }

        private void ClickCheck(List<Object_2D> ListIn)
        {
            for (int i = 0; i < ListIn.Count; i++)
            {
                /* Is the mouse inside our object's rectangle? */
                if (
                    ((_mouse.X > ListIn[i].Loc.X) && (_mouse.X < (ListIn[i].Loc.X + ListIn[i].Xsize))) &&
                    ((_mouse.Y > ListIn[i].Loc.Y) && (_mouse.Y < (ListIn[i].Loc.Y + ListIn[i].Ysize)))
                    )
                {
                    ListIn[i].Selected = true;
                }
                else
                {
                    ListIn[i].Selected = false;
                }
            }
        }
        public override void Draw(GameTime gameTime)
        {
            _spriteBatch.Begin(SpriteBlendMode.AlphaBlend);
            _spriteBatch.Draw(_mouseImage, new Vector2(_mouse.X, _mouse.Y), Color.Red);
            _spriteBatch.DrawString(ArialFont, String.Format("X: {0}, Y: {1}", _mouse.X, _mouse.Y), new Vector2(0.0f, 0.0f), Color.Black);
            _spriteBatch.End();
            base.Draw(gameTime);
        }
    }
}


